package com.zmn.oms.services.impl.serviceitem;

import com.alibaba.fastjson.JSON;
import com.zmn.base.price.common.constant.ItemCellConst;
import com.zmn.common.utils.number.NumberUtil;
import com.zmn.common.utils.string.StringUtil;
import com.zmn.oms.common.utils.EmojiUtil;
import com.zmn.oms.model.entity.serviceitem.OrderServiceItem;
import com.zmn.oms.model.entity.serviceitem.OrderServiceItemCell;
import com.zmn.oms.model.entity.serviceitem.OrderServiceItemDetail;
import com.zmn.oms.persistence.interfaces.serviceitem.OrderServiceItemCellDao;
import com.zmn.oms.persistence.interfaces.serviceitem.OrderServiceItemDao;
import com.zmn.oms.services.interfaces.serviceitem.OrderServiceItemService;
import io.shardingsphere.api.HintManager;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;

import javax.annotation.Resource;
import java.util.*;
import java.util.stream.Collectors;

/**
 * 类描述：订单服务项目
 *
 * @author heciqi
 * @date 2018/12/5 17:08
 */
@Service
public class OrderServiceItemServiceImpl implements OrderServiceItemService {

    @Resource
    private OrderServiceItemDao orderServiceItemDao;
    @Resource
    private OrderServiceItemCellDao orderServiceItemCellDao;

    /**
     * 按订单id查询扩展的产品数量
     *
     * @param orderId
     * @return
     */
    @Override
    public int countProExtIdByOrderId(Long orderId) {
        return orderServiceItemDao.countProExtIdByOrderId(orderId);
    }

    /**
     * 主键查询
     *
     * @param itemId
     * @return
     */
    @Override
    public OrderServiceItem selectByPrimaryKey(Long itemId) {
        OrderServiceItem orderServiceItem = orderServiceItemDao.selectByPrimaryKey(itemId);
        if (orderServiceItem != null) {
            List<OrderServiceItemCell> itemDetailList = orderServiceItemCellDao.findByOrderIdAndServItemId(orderServiceItem.getOrderId(), orderServiceItem.getServItemId());
            if (!CollectionUtils.isEmpty(itemDetailList)) {
                orderServiceItem.setItemDetailList(itemDetailList);
                orderServiceItem.setItemDetail(this.conversionSingleItemDetail(itemDetailList));
            }
        }
        return orderServiceItem;
    }


    @Override
    public List<OrderServiceItem> listOrderServiceItemByOrderIdList(List<Long> orderIdList) {
        try (HintManager hintManager = HintManager.getInstance()) {
            hintManager.setMasterRouteOnly();

            List<OrderServiceItem> orderServiceItems = orderServiceItemDao.listOrderServiceItemByOrderIdList(orderIdList);
            if (orderServiceItems == null || orderServiceItems.isEmpty()) {
                return orderServiceItems;
            }

            List<OrderServiceItemCell> orderServiceItemCells = orderServiceItemCellDao.listByOrderIdList(orderIdList);
            return processMapping(orderServiceItems, orderServiceItemCells);
        }
    }

    /**
     * 根据订单id查询服务项列表(主库)
     * 不含服务项明细
     * @param orderId
     * @return
     */
    @Override
    public List<OrderServiceItem> listByOrderIdSrcMaster(Long orderId) {
        try (HintManager hintManager = HintManager.getInstance()) {
            List<OrderServiceItem> orderServiceItems = orderServiceItemDao.listByOrderId(orderId);
            return orderServiceItems;
        }
    }

    /**
     * 根据订单id查询服务项列表
     *
     * @param orderId
     * @return
     */
    @Override
    public List<OrderServiceItem> listByOrderId(Long orderId) {
        List<OrderServiceItem> orderServiceItems = orderServiceItemDao.listByOrderId(orderId);
        if (orderServiceItems == null || orderServiceItems.isEmpty()) {
            return orderServiceItems;
        }

        List<OrderServiceItemCell> orderServiceItemCells = orderServiceItemCellDao.listByOrderId(orderId);
        return processMapping(orderServiceItems, orderServiceItemCells);
    }

    @Override
    public List<OrderServiceItem> listDynamicByOrderId(String query, Long orderId) {
        return orderServiceItemDao.listDynamicByOrderId(query, orderId);
    }

    /**
     * 根据订单id，产品扩展id查询服务项列表
     *
     * @param orderId
     * @return
     */
    @Override
    public List<OrderServiceItem> listByOrderIdAndProExtId(Long orderId, Long proExtId) {
        List<OrderServiceItem> orderServiceItems = this.listByOrderId(orderId);
        if (CollectionUtils.isEmpty(orderServiceItems)) {
            return orderServiceItems;
        }

        orderServiceItems = orderServiceItems.stream().filter(e -> e.getProExtId().equals(proExtId)).collect(Collectors.toList());
        if (CollectionUtils.isEmpty(orderServiceItems)) {
            return orderServiceItems;
        }

        List<OrderServiceItemCell> orderServiceItemCells = orderServiceItemCellDao.listByOrderId(orderId);

        return processMapping(orderServiceItems, orderServiceItemCells);
    }

    /**
     * 批量插入
     *
     * @param items
     * @return
     */
    @Override
    public Integer insertAll(List<OrderServiceItem> items) {
        if (CollectionUtils.isEmpty(items)) {
            return 0;
        }

        List<OrderServiceItemCell> details = new LinkedList<>();
        for (OrderServiceItem item : items) {
            if (StringUtil.isNotBlank(item.getCreater())) {
                item.setCreater(EmojiUtil.filterEmoji(item.getCreater()));
            }
            List<OrderServiceItemCell> detailList = item.getItemDetailList();
            if (!CollectionUtils.isEmpty(detailList)) {
                for (OrderServiceItemCell cell : detailList) {
                    cell.setCreater(item.getCreater());
                    cell.setOrderId(item.getOrderId());
                    cell.setWorkId(item.getOrderId());
                    cell.setProExtId(item.getProExtId());
                    cell.setServItemId(item.getServItemId());
                }
                details.addAll(detailList);
            }

            //处理内外部结算价
            if (NumberUtil.isNullOrZero(item.getExternalSettlementPrice())) {
                item.setExternalSettlementPrice(item.getItemPrice());
                item.setExternalTotalPrice(item.getTotalPrice());
            }
            if (NumberUtil.isNullOrZero(item.getInternalSettlementPrice())) {
                item.setInternalSettlementPrice(item.getItemPrice());
                item.setInternalTotalPrice(item.getTotalPrice());
            }
        }

        if (!details.isEmpty()) {
            orderServiceItemCellDao.insertAll(details);
        }
        return orderServiceItemDao.insertAll(items);
    }

    /**
     * 修改服务项
     *
     * @param orderServiceItem
     * @return
     */
    @Override
    public void updateByKey(OrderServiceItem orderServiceItem) {
        if (StringUtil.isNotBlank(orderServiceItem.getCreater())) {
            orderServiceItem.setCreater(EmojiUtil.filterEmoji(orderServiceItem.getCreater()));
        }
        orderServiceItemCellDao.deleteByOrderIdAndServiceItemId(orderServiceItem.getOrderId(), orderServiceItem.getServItemId());

        List<OrderServiceItemCell> detailList = orderServiceItem.getItemDetailList();
        if (!CollectionUtils.isEmpty(detailList)) {
            for (OrderServiceItemCell cell : detailList) {
                cell.setCreater(orderServiceItem.getCreater());
                cell.setOrderId(orderServiceItem.getOrderId());
                cell.setWorkId(orderServiceItem.getOrderId());
                cell.setProExtId(orderServiceItem.getProExtId());
                cell.setServItemId(orderServiceItem.getServItemId());
            }
            orderServiceItemCellDao.insertAll(detailList);
        }

        orderServiceItemDao.updateByKey(orderServiceItem);
    }

    /**
     * 修改服务项内部价
     *
     * @param orderServiceItem
     * @return void
     * @author wangxiaokun
     */
    @Override
    public void updateInternalPriceByKey(OrderServiceItem orderServiceItem) {
        if (StringUtil.isNotBlank(orderServiceItem.getCreater())) {
            orderServiceItem.setCreater(EmojiUtil.filterEmoji(orderServiceItem.getCreater()));
        }
        orderServiceItemDao.updateByKey(orderServiceItem);
    }

    /**
     * 主键删除
     *
     * @param itemId
     * @return
     */
    @Override
    public Integer deleteByPrimaryKey(Long itemId) {
        OrderServiceItem item = orderServiceItemDao.selectByPrimaryKey(itemId);
        if (item == null) {
            return 0;
        }

        orderServiceItemCellDao.deleteByOrderIdAndServiceItemId(item.getOrderId(), item.getServItemId());

        return orderServiceItemDao.deleteByPrimaryKey(itemId);
    }

    /**
     * 按产品扩展id删除
     *
     * @param proExtId
     * @return
     */
    @Override
    public Integer deleteByProExtId(Long proExtId) {
        orderServiceItemCellDao.deleteByProExtId(proExtId);
        return orderServiceItemDao.deleteByProExtId(proExtId);
    }

    /**
     * 按订单id删除
     *
     * @param orderId
     * @return
     */
    @Override
    public Integer deleteByOrderId(Long orderId) {
        orderServiceItemCellDao.deleteByOrderId(orderId);
        return orderServiceItemDao.deleteByOrderId(orderId);
    }

    /**
     * 按订单id,服务项id删除
     *
     * @param orderId
     * @return
     */
    @Override
    public Integer deleteByOrderIdAndServiceItemId(Long orderId, Integer servItemId) {
        orderServiceItemCellDao.deleteByOrderIdAndServiceItemId(orderId, servItemId);
        return orderServiceItemDao.deleteByOrderIdAndServiceItemId(orderId, servItemId);
    }

    /**
     * 处理映射关系，为服务型匹配对应的明细信息
     * @param itemList
     * @param detailList
     * @return
     */
    private List<OrderServiceItem> processMapping(List<OrderServiceItem> itemList, List<OrderServiceItemCell> detailList) {
        if (CollectionUtils.isEmpty(itemList) || CollectionUtils.isEmpty(detailList)) {
            return itemList;
        }

        Map<String, List<OrderServiceItemCell>> newItemDetailMap = detailList
                .stream()
                .collect(Collectors.groupingBy(this::getItemDetailKey));
        Map<String, OrderServiceItemDetail> itemDetailMap = this.conversionMultiItemDetail(detailList);

        // 给服务项匹配明细
        for (OrderServiceItem item : itemList) {
            String key = this.getItemDetailKey(item);
            item.setItemDetail(itemDetailMap.get(key));
            item.setItemDetailList(newItemDetailMap.get(key));
        }
        return itemList;
    }

    private Map<String,OrderServiceItemDetail> conversionMultiItemDetail(List<OrderServiceItemCell> itemCells) {
        if (CollectionUtils.isEmpty(itemCells)) {
            return null;
        }
        Map<String, OrderServiceItemDetail> itemDetailMap = new HashMap<>();
        itemCells.stream()
                .collect(Collectors.groupingBy(this::getItemDetailKey))
                .forEach((k,v)->{
                    if (StringUtil.isBlank(k)) {
                        return;
                    }
                    OrderServiceItemCell cell1 = v.get(0);
                    OrderServiceItemDetail itemDetail = new OrderServiceItemDetail();
                    itemDetail.setOrderId(cell1.getOrderId());
                    itemDetail.setProExtId(cell1.getProExtId());
                    itemDetail.setServItemId(cell1.getServItemId());
                    this.setDetailPrice(v, itemDetail);
                    itemDetailMap.put(k, itemDetail);
                });
        return itemDetailMap;
    }

    private OrderServiceItemDetail conversionSingleItemDetail(List<OrderServiceItemCell> itemCells){
        if (CollectionUtils.isEmpty(itemCells)) {
            return null;
        }
        OrderServiceItemCell cell1 = itemCells.get(0);
        OrderServiceItemDetail itemDetail = new OrderServiceItemDetail();
        itemDetail.setOrderId(cell1.getOrderId());
        itemDetail.setProExtId(cell1.getProExtId());
        itemDetail.setServItemId(cell1.getServItemId());
        this.setDetailPrice(itemCells, itemDetail);
        return itemDetail;
    }

    private void setDetailPrice(List<OrderServiceItemCell> itemCells, OrderServiceItemDetail itemDetail) {
        for (OrderServiceItemCell cell : itemCells) {
            switch (cell.getItemCellId()) {
                case ItemCellConst.ITEM_CELL_SERV:
                    itemDetail.setServicePrice(cell.getCellPrice());
                    break;
                case ItemCellConst.ITEM_CELL_PART:
                    itemDetail.setPartPrice(cell.getCellPrice());
                    break;
                case ItemCellConst.ITEM_CELL_HOUR:
                    itemDetail.setHourFee(cell.getCellPrice());
                    break;
                case ItemCellConst.ITEM_CELL_TRIP:
                    itemDetail.setTrafficFee(cell.getCellPrice());
                    break;
                case ItemCellConst.ITEM_CELL_CHECK:
                    itemDetail.setCheckFee(cell.getCellPrice());
                    break;
                case ItemCellConst.ITEM_CELL_TECH:
                    itemDetail.setTechnologyFee(cell.getCellPrice());
                    break;
                case ItemCellConst.ITEM_CELL_WARRANT:
                    itemDetail.setGuaranteeFee(cell.getCellPrice());
                    break;
            }
        }
    }

    private String getItemDetailKey(OrderServiceItemCell itemCell) {
        if (Objects.isNull(itemCell)) {
            return null;
        }
        return String.format("%s%s%s%s", itemCell.getOrderId(), itemCell.getWorkId(), itemCell.getProExtId(), itemCell.getServItemId());
    }

    private String getItemDetailKey(OrderServiceItem item) {
        if (Objects.isNull(item)) {
            return null;
        }
        return String.format("%s%s%s%s", item.getOrderId(), item.getOrderId(), item.getProExtId(), item.getServItemId());
    }
}
